import express from "express";
import fs from "fs";
import path from "path";
import etag from "etag";

const app = express();

/*
  http缓存：强制缓存和协商缓存
    第一次（没有缓存）：
      浏览器向服务器发送请求，请求某个资源
      服务器返回该资源，同时在响应头设置缓存字段：
        强制缓存：
          cache-control(http 1.1): max-age=3600
          expires(http 1.0): new Date(Date.now() + 3600000).toGMTString()
        协商缓存：
          etag 文件内容唯一标识
          last-modified 文件最近修改时间
    第二次（走缓存）：
      浏览器将要向服务器发送请求，发送请求之前，先判断该资源是否命中强制缓存
      如果命中强制缓存，直接读取缓存，响应状态码200

      如果没有命中强制缓存，发送请求给服务器，此时会自动携带两个请求头字段：
        协商缓存：
          if-none-match(之前etag的值)
          if-modified-since(之前last-modified的值)
      发送给服务器，服务器读取文件内容得到 etag 和 last-modified，将其与 if-none-match 和 if-modified-since进行比较
      如果相等，说明命中协商缓存，返回响应状态码304
      如果不相等，说明没有命中缓存，返回新的资源和新的强制缓存和协商缓存字段。此时响应状态码200
*/
app.get("/", (req, res) => {
  const html = fs.readFileSync(path.resolve("public/index.html"));
  res.setHeader("content-type", "text/html;chartset=utf-8;");
  res.send(html);
});

app.get("/js/index.js", (req, res) => {
  const js = fs.readFileSync(path.resolve("public/js/index.js"));
  const etagStr = etag(js);
  const ifNoneMatch = req.headers["if-none-match"];
  if (ifNoneMatch === etagStr) {
    // 命中协商缓存
    res.status(304).end();
    return;
  }

  // 没有命中任何缓存
  res.setHeader("content-type", "text/javascript");
  res.setHeader("cache-control", "max-age=10");
  res.setHeader("etag", etag(js));
  res.send(js);
});

app.listen(3000, (err) => {
  if (err) console.log(err);
  else console.log("服务器启动成功了");
});
